/**
 * @ Author: luoqi
 * @ Create Time: 2024-03-14 10:53
 * @ Modified by: luoqi
 * @ Modified time: 2024-03-15 17:16
 * @ Description:
 */

#ifndef _QSYNC_H
#define _QSYNC_H

#include <stdint.h>
#include "qlink.h"
#include "../algo/list.h"

typedef int(*QSyncTopicCb)(void *args, int size);
typedef struct qsync_topic {
    const char *topic;
    uint16_t id;
    QSyncTopicCb callback;

    QList sync_node;
} QSyncTopic;

#ifndef QSYNC_BUF_SIZE
#define QSYNC_BUF_SIZE     64
#endif

/** 
 * QSync using QLink to transmit synchronize data.
 * But there some differece between QSync and QLink:
 *  - Qsync using QLink.serial and QLink.type as qsync 
 *    topic id.
 *  - QSyncTopic.id = (QLink.serial << 8) | QLink.type.
 */
typedef struct proto_sync {
    uint32_t topic_num;
    uint8_t framebuf[QSYNC_BUF_SIZE];
    uint8_t rbuf[QSYNC_BUF_SIZE];
    QLink link;

    QList sync_list;
} QSyncLink;

typedef int (*QSyncSend)(uint8_t *data, int len);
typedef int (*QSyncRecv)(uint8_t *buf, int len);

int qsync_init(QSyncLink *sync, QSyncSend send, QSyncRecv recv);

int qsync_topic_init(QSyncTopic *topic, const char *name, QSyncTopicCb callback);

int qsync_topic_register(QSyncLink *sync, QSyncTopic *topic);

int qsync_send(QSyncLink *sync, const char *topic, uint8_t *data, uint8_t size);

int qsync_recv(QSyncLink *sync, int size);

int qsync_exec(QSyncLink *sync);

#endif
